package band.wukong.practice.webservice.kh.sample04;

import javax.xml.stream.*;
import javax.xml.stream.events.XMLEvent;
import java.io.*;

/**
 * @author wukong(wukonggg@139.com)
 */
public class JAXPSampleOfStreamingAPI {

    public static void main(String[] args) throws Exception {
        parseByCursor();
        parseByEventIterator();
        parseByparseByEventIteratorWithEventFilter();
        createXmlByStreamWriter();
    }

    /**
     * read基于stream，光标模型
     */
    public static void parseByCursor() {
        InputStream is = prepearInputStream();

        XMLInputFactory factory = XMLInputFactory.newInstance();
        try {
            XMLStreamReader reader = factory.createXMLStreamReader(is);
            while (reader.hasNext()) {
                int type = reader.next();
                parseByCursorDetail(type, reader);
            }
        } catch (XMLStreamException e) {
            e.printStackTrace();
            System.exit(-1);
        } finally {
            try {
                is.close();
            } catch (IOException e) {
                e.printStackTrace();
                System.exit(-1);
            }
        }
    }

    private static void parseByCursorDetail(int type, XMLStreamReader reader) throws XMLStreamException {
        if (type == XMLStreamConstants.START_ELEMENT) {
            String name = reader.getName().toString();
//                    if (name.equals("book")) {
//                        System.out.print("[ET_S] ");
//                        System.out.println(reader.getAttributeName(0) + "=" + reader.getAttributeValue(0));
//                    }
            if (name.equals("title")) {
                System.out.print(reader.getElementText() + ":");
            }
            if (name.equals("price")) {
                System.out.println(reader.getElementText() + "\n");
            }
        }
//                else if (type == XMLStreamConstants.END_ELEMENT) {
//                    System.out.print("[ET_E] ");
//                    System.out.println("/" + reader.getName());
//                } else if (type == XMLStreamConstants.CHARACTERS) {
//                    System.out.print("[CHAR] ");
//                    System.out.println(reader.getText());
//                }
    }


    /**
     * read基于evnet，迭代模型
     */
    public static void parseByEventIterator() {
        InputStream is = prepearInputStream();

        XMLInputFactory factory = XMLInputFactory.newInstance();
        try {
            XMLEventReader reader = factory.createXMLEventReader(is);
            while (reader.hasNext()) {
                XMLEvent event = reader.nextEvent();
                parseByEventIteratorDetail(event, reader);
            }
        } catch (XMLStreamException e) {
            e.printStackTrace();
            System.exit(-1);
        } finally {
            try {
                is.close();
            } catch (IOException e) {
                e.printStackTrace();
                System.exit(-1);
            }
        }
    }

    private static void parseByEventIteratorDetail(XMLEvent event, XMLEventReader reader) throws XMLStreamException {
        if (event.isStartElement()) {
            String name = event.asStartElement().getName().toString();
            if (name.equals("title")) {
                System.out.print(reader.getElementText() + ":");
            }
            if (name.equals("price")) {
                System.out.println(reader.getElementText() + "\n");
            }
        }
    }

    /**
     * read基于evnet，迭代模型，使用过滤器
     */
    public static void parseByparseByEventIteratorWithEventFilter() {
        InputStream is = prepearInputStream();

        XMLInputFactory factory = XMLInputFactory.newInstance();
        try {
            XMLEventReader reader = factory.createFilteredReader(factory.createXMLEventReader(is)
                    , new EventFilter() {
                        @Override
                        public boolean accept(XMLEvent event) {
//                            return event.isStartElement();
                            if (event.isStartElement()) {
                                String name = event.asStartElement().getName().toString();
                                return name.equals("title") || name.equals("price");
                            }
                            return false;
                        }
                    });
            while (reader.hasNext()) {
                XMLEvent event = reader.nextEvent();
                parseByEventIteratorDetail(event, reader);
            }
        } catch (XMLStreamException e) {
            e.printStackTrace();
            System.exit(-1);
        } finally {
            try {
                is.close();
            } catch (IOException e) {
                e.printStackTrace();
                System.exit(-1);
            }
        }
    }

    private static InputStream prepearInputStream() {
        final String xmlPath = "./src/main/java/band/wukong/practice/webservice/kh/sample04/books.xml";
        InputStream is = null;
        try {
            is = new FileInputStream(new File(xmlPath));
        } catch (FileNotFoundException e) {
            e.printStackTrace();
            System.exit(-1);
        }
        return is;
    }

    /**
     * 这个例子没有完成定义命名空间
     */
    public static void createXmlByStreamWriter() {
        XMLStreamWriter writer = null;
        try {
            writer = XMLOutputFactory.newInstance().createXMLStreamWriter(System.out);
            writer.writeStartDocument("UTF-8", "1.0");
            writer.writeEndDocument();
            String ns = "http://band.wukong/lin";
            writer.writeStartElement("wk", "person", ns);
            writer.writeStartElement("wk", "id", ns);
//            writer.writeStartElement("id");
            writer.writeCharacters("1");
            writer.writeEndElement();
            writer.writeEndElement();

            writer.flush();
        } catch (XMLStreamException e) {
            e.printStackTrace();
        } finally {
            try {
                if (writer != null) {
                    writer.close();
                }
            } catch (XMLStreamException e) {
                e.printStackTrace();
            }
        }
    }

}
